package cn.sciento.farm.devicemanager.api.jsonrpc.impl;


import cn.sciento.farm.devicemanager.api.jsonrpc.ControllerJsonApi;
import cn.sciento.farm.devicemanager.common.constant.ResultConstant;
import cn.sciento.farm.devicemanager.common.util.DateUtil;
import cn.sciento.farm.devicemanager.common.util.ReturnUtil;
import cn.sciento.farm.devicemanager.dao.entity.DevController;
import cn.sciento.farm.devicemanager.dao.entity.DevControllerLog;
import cn.sciento.farm.devicemanager.dao.entity.DevDevice;
import cn.sciento.farm.devicemanager.dao.entity.DevTimer;
import cn.sciento.farm.devicemanager.dao.model.ControllerNumber;
import cn.sciento.farm.devicemanager.dao.model.PageConditionQuery;
import cn.sciento.farm.devicemanager.dao.model.ResponseMessage;
import cn.sciento.farm.devicemanager.dao.model.StrategyInfo;
import cn.sciento.farm.devicemanager.service.*;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.googlecode.jsonrpc4j.spring.AutoJsonRpcServiceImpl;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

@Service
@AutoJsonRpcServiceImpl
public class ControllerJsonApiImpl implements ControllerJsonApi {

    @Autowired
    ControllerService controllerService;

    @Autowired
    DeviceService deviceService;

    @Autowired
    DeviceControlService deviceControlService;

    @Autowired
    TimerService timerService;

    @Autowired
    StrategyService strategyService;

    @Autowired
    ControllerLogService controllerLogService;

    @Override
    public ResponseMessage update(DevController controller) {
        if (controller.getId() <= 0) {
            return ReturnUtil.getReturnMap(ResultConstant.NULL_PARAMETER);
        } else {
            DevController devController = new DevController();
            devController.setId(controller.getId());
            devController.setName(controller.getName());
            devController.setOnline(controller.getOnline());
            devController.setSequence(controller.getSequence());
            devController.setRelatedEquip(controller.getRelatedEquip());
            int count = controllerService.updateById(devController);
            return ReturnUtil.getReturnMap(ResultConstant.SUCCESS, count, devController.getId());

        }
    }

    @Override
    public ResponseMessage delete(Long id) {
        int count = controllerService.deleteById(id);
        return ReturnUtil.getReturnMap(ResultConstant.SUCCESS, count);
    }

    @Override
    public ResponseMessage list(String eui, Integer landId) {
        if (StringUtils.isEmpty(eui) && landId <= 0) {
            return ReturnUtil.getReturnMap(ResultConstant.NULL_PARAMETER);
        } else {
            List<DevController> controllerList = getDeviceList(eui, landId);


            return ReturnUtil.getReturnMap(ResultConstant.SUCCESS, controllerList);
        }
    }

    private List<DevController> getDeviceList(String eui, Integer landId) {
        List<DevController> controllerList = new ArrayList<>();
        if (StringUtils.isEmpty(eui)) {
            controllerList = controllerService.getByLandId(landId);
        } else {
            controllerList = controllerService.getByEui(eui);
        }
        return controllerList;
    }

    @Override
    public ResponseMessage listAll(String eui, Integer landId) {
        List<DevController> controllerList = getDeviceList(eui, landId);
        List<DevController> deviceSwitches = getDeviceLimit(controllerList);
        List<ControllerNumber> deviceSwitchNumbers = new ArrayList<>();
        for (DevController deviceSwitch : deviceSwitches) {
            ControllerNumber deviceSwitchNumber = new ControllerNumber();
            BeanUtils.copyProperties(deviceSwitch, deviceSwitchNumber);
            List<DevTimer> deviceSwitchTimerList = timerService.getByControllerId(deviceSwitch.getId());
            List<StrategyInfo> strategyList = strategyService.getByControllerId(deviceSwitch.getId());
            deviceSwitchNumber.setStrategy(strategyList.size());
            deviceSwitchNumber.setStrategyList(strategyList);
            deviceSwitchNumber.setTimer(deviceSwitchTimerList.size());
            deviceSwitchNumber.setTimerList(deviceSwitchTimerList);
            deviceSwitchNumbers.add(deviceSwitchNumber);
        }
        return ReturnUtil.getReturnMap(ResultConstant.SUCCESS, deviceSwitchNumbers);
    }

    private List<DevController> getDeviceLimit(List<DevController> deviceSwitches) {
        List<DevController> relateSwtichs = new ArrayList<>();
        List<DevController> baseSwitchs = new ArrayList<>();
        for (DevController deviceSwitch : deviceSwitches) {
            if (deviceSwitch.getRelatedEquip() == 0) {
                baseSwitchs.add(deviceSwitch);
            } else {
                relateSwtichs.add(deviceSwitch);
            }
        }
        for (DevController deviceSwitch : relateSwtichs) {
            long relatedSwitchId = deviceSwitch.getRelatedEquip();
            DevController relatedSwitch = null;
            int index = -1;
            for (int i = 0; i < baseSwitchs.size(); i++) {
                if (baseSwitchs.get(i).getId().equals(relatedSwitchId)) {
                    relatedSwitch = baseSwitchs.get(i);
                    index = i;
                    break;
                }
            }
            if (relatedSwitch != null) {
                int relateSwitchStatus = deviceSwitch.getStatus();
                int relatedSwitchStatus = relatedSwitch.getStatus();
                if (relateSwitchStatus == 0 && relatedSwitchStatus == 1) {
                    deviceSwitch.setStatus(2);
                }
                baseSwitchs.remove(index);
            }

        }
        // TODO 这里应该有个排序
        relateSwtichs.addAll(baseSwitchs);
        return relateSwtichs;
    }

    @Override
    public ResponseMessage get(Long id) {
        DevController devController = controllerService.getById(id);
        if (devController == null) {
            return ReturnUtil.getReturnMap(ResultConstant.NULL_PARAMETER);
        } else {
            return ReturnUtil.getReturnMap(ResultConstant.SUCCESS, devController);

        }
    }

    @Override
    public ResponseMessage control(Long controllerId, Integer sw) {
        int count = deviceControlService.sendBlockControl(controllerId, sw);
        return ReturnUtil.getReturnMap(ResultConstant.SUCCESS, count);

    }

    @Override
    public ResponseMessage listSameNode(Long id) {
        List<DevController> devControllers = controllerService.getSameNode(id);
        return ReturnUtil.getReturnMap(ResultConstant.SUCCESS, devControllers);

    }

    @Override
    public ResponseMessage getControllerLog(PageConditionQuery data) {
        if (data == null || data.getAreaId() == null
                || data.getAreaId() < 1
                || data.getControllerId() < 0
                || data.getCurrentPage() < 1
                || data.getPageSize() < 1
        ){
            return ReturnUtil.getReturnMap(ResultConstant.NULL_PARAMETER);
        }
        if (data.getCurrentPage() == null ){
            data.setCurrentPage(1);
        }
        if (data.getPageSize()== null){
            data.setPageSize(10);
        }
        if (data.getBeginTime() == null){
            Date date = DateUtil.getTodayZeroHour();
            data.setBeginTime(date.getTime());
        }
        if ( data.getEndTime() == null) {
            Date date = DateUtil.getTodayLastHour();
            data.setEndTime(date.getTime());
        }
        IPage<DevControllerLog> timerLogs = controllerLogService.getControllerLog(data);
        return ReturnUtil.getReturnMap(ResultConstant.SUCCESS,timerLogs);
    }
}
